package com.base.monitor.framework.util;

import com.base.monitor.framework.properties.SystemProperties;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.stereotype.Component;

import javax.annotation.PostConstruct;
import java.io.*;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.util.*;

@Component
@EnableConfigurationProperties(SystemProperties.class)
public class DiskUtils {

    @Autowired
    private SystemProperties systemProperties;

    private String fileLocation;

    @PostConstruct
    public void initFileLocation() {
        fileLocation = "application-" + systemProperties.getActive() + ".properties";
    }
    /**
     * 更新properties文件
     * @param key 键名
     * @param value 值
     */
    public void updatePropertiesFile(String key, String value) {
        Properties prop = loadPropertiesFile(fileLocation);
        prop.setProperty(key, value);
        // 文件输出流
        try {
            FileOutputStream fos = new FileOutputStream(fileLocation);
            // 将Properties集合保存到流中
            prop.store(fos, null);
            fos.close();// 关闭流
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    /**
     * 读取properties文件
     * @param path 文件路径
     * @return
     */
    private Properties loadPropertiesFile(String path) {
        Properties prop = new Properties();
        File file = new File(path);
        if (!file.exists()) {
            try {
                file.createNewFile();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        FileInputStream fis;
        try {
            fis = new FileInputStream(file);
            prop.load(fis);
            fis.close();// 关闭流
        } catch (IOException e) {
            e.printStackTrace();
        }
        return prop;
    }

    /**使用FileOutputStream来写入txt文件
     * @param txtPath txt文件路径
     * @param content 需要写入的文本
     */
    public static void writeTxt(String txtPath, String content) {
        FileOutputStream fileOutputStream = null;
        File file = new File(txtPath);
        try {
            if (file.exists()) {
                //判断文件是否存在，如果不存在就新建一个txt
                file.createNewFile();
            }
            fileOutputStream = new FileOutputStream(file, true);
            fileOutputStream.write(content.getBytes());
            fileOutputStream.flush();
            fileOutputStream.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * 读取文件最后几行 <br>
     * 相当于Linux系统中的tail命令 读取大小限制是2GB
     *
     * @param filename 文件名
     * @param charset  文件编码格式,传null默认使用defaultCharset
     * @param rows     读取行数
     * @throws IOException IOException
     */
    public static String readLastRows(String filename, Charset charset, int rows) {
        charset = charset == null ? Charset.defaultCharset() : charset;
        byte[] lineSeparator = System.getProperty("line.separator").getBytes();
        try (RandomAccessFile rf = new RandomAccessFile(filename, "r")) {
            // 每次读取的字节数要和系统换行符大小一致
            byte[] c = new byte[lineSeparator.length];
            // 在获取到指定行数和读完文档之前,从文档末尾向前移动指针,遍历文档每一个字节
            for (long pointer = rf.length(), lineSeparatorNum = 0; pointer >= 0 && lineSeparatorNum < rows;) {
                // 移动指针
                rf.seek(pointer--);
                // 读取数据
                int readLength = rf.read(c);
                if (readLength != -1 && Arrays.equals(lineSeparator,c)) {
                    lineSeparatorNum++;
                }
                //扫描完依然没有找到足够的行数,将指针归0
                if (pointer == -1 && lineSeparatorNum < rows) {
                    rf.seek(0);
                }
            }
            byte[] tempbytes = new byte[(int) (rf.length() - rf.getFilePointer())];
            rf.readFully(tempbytes);
            return new String(tempbytes, charset);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    // 获取符合条件的采集文件的路径
    public static String getWholeCollectFileName(String collectFileLocation) {
        return collectFileLocation
                + "-" + ConcurrentUtil.format(new Date(), "yyyy-MM-dd") + ".txt";
    }

    public static void main(String[] args) {
        String s = readLastRows("collect.txt", StandardCharsets.UTF_8, 5);
        List<String> split = new ArrayList<>(Arrays.asList(s.split("\r\n")));
        System.out.println(split);
    }
}
